package com.contactsconverter.service;

import java.util.ArrayList;

import org.json.JSONException;
import org.json.JSONObject;

import com.android.volley.Response;
import com.android.volley.VolleyError;
import com.android.volley.Request.Method;
import com.android.volley.toolbox.JsonObjectRequest;
import com.contactsconverter.activity.CTLoginActivity;
import com.contactsconverter.activity.CTSynchroniserActivity;
import com.contactsconverter.utils.CTUtils;
import com.contactsconverter.volley.CTRequestQueue;
import com.contactsconverter.R;
import com.difsonapps.contacttranslator.dto.ContactDTO;
import com.difsonapps.contacttranslator.dto.EmailDTO;
import com.difsonapps.contacttranslator.dto.EmailTypeEnum;
import com.difsonapps.contacttranslator.dto.NumberDTO;
import com.difsonapps.contacttranslator.dto.NumberTypeEnum;
import com.difsonapps.contacttranslator.dto.SocialContactDTO;
import com.difsonapps.contacttranslator.dto.UserDTO;
import com.google.gson.Gson;

import android.accounts.Account;
import android.accounts.AccountManager;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.database.Cursor;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.IBinder;
import android.provider.ContactsContract;
import android.support.v4.app.NotificationCompat;
import android.support.v4.app.TaskStackBuilder;
import android.telephony.TelephonyManager;
import android.util.Log;

public class CTSynchroniseService extends AsyncTask<Context, Void, String>{

	static final String SELECTION = "(" + ContactsContract.Data.DISPLAY_NAME+ " NOTNULL) AND (" + ContactsContract.Data.DISPLAY_NAME+ " != '' )";
	private  String mAccountName = "";
	private String SAVECONTACTSERVICE = "rest/contact/save";
	int counter = 0;
	private boolean b = false;
	private NotificationCompat.Builder mBuilder;
	private NotificationManager mNotificationManager;
	public final static Object lock = new Object();
	private boolean waitBefore = true;
	private boolean update = true;
	private int nbreContactSave = 0;
	private int nomberTotalDeContact ;
	private int numMessages;
	public Context context;

	
	@Override
	protected String doInBackground(Context... params) {
		this.context = params[0];
		onCreate();
		Log.e("Koi?", "c est la fin");
		return "OK";
	}

	
	@Override
	protected void onPostExecute(String result) {
	}

	@Override
	protected void onPreExecute() {
	}

	@Override
	protected void onProgressUpdate(Void... values) {
	}
	

	public void onCreate() {

		Account[] accounts = AccountManager.get(this.context).getAccountsByType(CTUtils.ACCOUNT_TYPE);
		mAccountName = accounts[0].name;
				mBuilder =
				        new NotificationCompat.Builder(this.context)
				        .setSmallIcon(R.drawable.event)
				        .setContentTitle(this.context.getString(R.string.ct_notification_title))
				        .setContentText(this.context.getString(R.string.ct_notification_content));
				// Creates an explicit intent for an Activity in your app
				Intent resultIntent = new Intent();
		
				// The stack builder object will contain an artificial back stack for the
				// started Activity.
				// This ensures that navigating backward from the Activity leads out of
				// your application to the Home screen.
				TaskStackBuilder stackBuilder = TaskStackBuilder.create(this.context);
				// Adds the back stack for the Intent (but not the Intent itself)
				////stackBuilder.addParentStack(CTSynchroniserActivity.class);
				// Adds the Intent that starts the Activity to the top of the stack
				stackBuilder.addNextIntent(resultIntent);
				PendingIntent resultPendingIntent =
				        stackBuilder.getPendingIntent(
				            0,
				            PendingIntent.FLAG_UPDATE_CURRENT
				        );
				mBuilder.setContentIntent(resultPendingIntent);
		mNotificationManager =
				(NotificationManager) this.context.getSystemService(Context.NOTIFICATION_SERVICE);
				// mId allows you to update the notification later on.
				mNotificationManager.notify(CTUtils.synchonisation_save, mBuilder.build());
				numMessages = 0;
				

		saveAll();
	}

	private void saveAll(){

		Uri contactsUri = ContactsContract.Contacts.CONTENT_URI;
		Cursor contactsCursor = this.context.getContentResolver().query(contactsUri, null, SELECTION, null, null);
		UserDTO user = new UserDTO();
		user.setEmail(mAccountName);
		ContactDTO contactDTO = new ContactDTO();
		contactDTO.setUser(user);
		try{
			nomberTotalDeContact = contactsCursor.getCount();
			mBuilder.setProgress(nomberTotalDeContact, 0, true);
			if (nomberTotalDeContact > 0) {
				while (contactsCursor.moveToNext()) {
					
						waitBefore = false;
						//recuperation du contact id
						long contactId = contactsCursor.getLong(contactsCursor.getColumnIndex("_ID"));
						contactDTO.setContactId(contactId+"");
						//recuperation device id
						TelephonyManager telephonyManager = (TelephonyManager)this.context.getSystemService(Context.TELEPHONY_SERVICE);					
						contactDTO.setDeviceId(telephonyManager.getDeviceId()+"");
						//recuperation du display name
						Uri dataUri = ContactsContract.Data.CONTENT_URI;
						Cursor dataCursor = this.context.getContentResolver().query(dataUri, null, ContactsContract.Data.CONTACT_ID + "=" + contactId, null, null);
						dataCursor.moveToFirst();
						String displayName = dataCursor.getString(dataCursor.getColumnIndex(ContactsContract.Data.DISPLAY_NAME ));
						contactDTO.setDisplayName(displayName);					
						//recuperation du nickname
						//					String nickName = dataCursor.getString(dataCursor.getColumnIndex(ContactsContract.Data.n ));
						//					contactDTO.setNickName(nickName);

						contactDTO.setNumberDTOs(new ArrayList<NumberDTO>());
						if (Integer .parseInt(contactsCursor.getString(contactsCursor .getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER))) > 0) {

							Cursor pCur = this.context.getContentResolver().
									query( ContactsContract.CommonDataKinds.Phone.CONTENT_URI, 
											null, ContactsContract.CommonDataKinds.Phone.CONTACT_ID + " = ?", new String[] { contactId+"" }, null); 
							while (pCur.moveToNext()) { 
								String phone  = pCur .getString(pCur .getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
								int phoneType  = pCur .getInt(pCur .getColumnIndex(ContactsContract.CommonDataKinds.Phone.TYPE));
								NumberDTO numberDTO = new NumberDTO(phone,  NumberTypeEnum.get(phoneType)); 
								contactDTO.getNumberDTOs().add(numberDTO);
							}
							pCur.close(); 				
						}
						Cursor emailCur = this.context.getContentResolver().query(ContactsContract.CommonDataKinds.Email.CONTENT_URI,null,
								ContactsContract.CommonDataKinds.Email.CONTACT_ID + " = ?", new String[]{contactId+""},null); 
						contactDTO.setEmailDTOs(new ArrayList<EmailDTO>());
						while (emailCur.moveToNext()) { 
							String email = emailCur.getString( emailCur.getColumnIndex(ContactsContract.CommonDataKinds.Email.DATA));	
							int emailType = emailCur .getInt(emailCur.getColumnIndex(ContactsContract.CommonDataKinds.Email.TYPE));
							EmailDTO emailDTO = new EmailDTO(email, EmailTypeEnum.get(emailType));
							contactDTO.getEmailDTOs().add(emailDTO);
						} 
						emailCur.close();
						contactDTO.setSocialContactDTOs(new ArrayList<SocialContactDTO>());

						String url = this.context.getString(R.string.default_server_url);
						url += SAVECONTACTSERVICE;
						//Log.e(CTSynchroniseService.class.getName(), url);
						if(contactDTO.getEmailDTOs().size()>0 || contactDTO.getNumberDTOs().size()>0)
						{
							saveOne(contactDTO, url);
						}
						
					
				}
				
				
				mNotificationManager.cancel(CTUtils.synchonisation_save);
				Intent resultIntent = new Intent(this.context,CTSynchroniserActivity.class);
				TaskStackBuilder stackBuilder = TaskStackBuilder.create(this.context);
				stackBuilder.addParentStack(CTSynchroniserActivity.class);
				stackBuilder.addNextIntent(resultIntent);
				PendingIntent resultPendingIntent =
				        stackBuilder.getPendingIntent(
				            0,
				            PendingIntent.FLAG_UPDATE_CURRENT
				        );
				mBuilder.setContentIntent(resultPendingIntent);
				mNotificationManager =(NotificationManager) this.context.getSystemService(Context.NOTIFICATION_SERVICE);
				mBuilder.setContentText(this.context.getString(R.string.ct_synchronisation_save_end)).setProgress(0,0,false);
				mNotificationManager.notify(CTUtils.synchonisation_save, mBuilder.build());
				
				update = false;
			}
		}catch (Exception e) {
			Log.e(CTSynchroniseService.class.getName(), e.getMessage()+"");
		}
	}

	private boolean saveOne(ContactDTO contact , String url){


		
		mBuilder.setContentText(contact.getDisplayName()).setNumber(++numMessages);
		mNotificationManager.notify(CTUtils.synchonisation_save, mBuilder.build());
		Gson gson = new Gson();
		String flat = gson.toJson(contact);
		//Log.e("JSONObject", flat);
		JSONObject postData;
		try {
			postData = new JSONObject(flat);
			JsonObjectRequest jsObjRequest = new JsonObjectRequest
					(Method.POST, url ,postData, new Response.Listener<JSONObject>() {

						@Override
						public void onResponse(JSONObject jsonObject) {
							//Log.e(CTLoginActivity.class.getName(), jsonObject+" <----- Taponno");
							nbreContactSave++;
							//mBuilder.setProgress(nomberTotalDeContact, nbreContactSave, false);
							b = true;
						}
					}, new Response.ErrorListener() {
						@Override
						public void onErrorResponse(VolleyError error) {
							Log.e(CTLoginActivity.class.getName(), "Mauvais");
							error.printStackTrace();
							b = false;
						}
					});
			CTRequestQueue.getInstance(this.context.getApplicationContext()).addToRequestQueue(jsObjRequest);
		} catch (JSONException e1) {

			e1.printStackTrace();
			Log.e(CTSynchroniseService.class.getName(), e1.getMessage()+"");
		}
		

		return b;
	}
	
	
}
